﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Data;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using grap;


namespace DiaryPlanner.Diary
{
    public partial class draw_panel : UserControl
    {
        /// 필수 디자이너 변수입니다.
        /// 

        //private System.ComponentModel.Container components = null;
        //private int red, green, blue;
        private string tool;
        private const string LineTool = "Line";
        private const string RectangleTool = "Rectangle";
        private const string ElipseTool = "Elipse";
        private const string EraseTool = "Erase";
        private bool fillOrNot = false;
        private const bool Fill = true;
        private const bool NotFill = false;
        private Point start;
        private Point end;
        private bool mouseDownOrNot;
        private const bool MouseDownState = true;
        private const bool MouseUpState = false;
        private Pen drawingPen;
        
        ////////
        ////moving write를 수행하기 위해 선언된 class
        private GDI32 gdi = new GDI32();
        private Point oldMouse, mouseDownAt;

        private Graphics g;
        private float width;
        private float height;
        private SolidBrush fillBrush;
        private Color foreColor; //색깔에 대한 변수
        private int eraserSize; // 지우개의 크기를 결정하는 변수
        private int erase_check = 0; //지우개 변수 확인

        DiaryPlanner.Diary.pic_draw_add pic_draw_add_object;

        public draw_panel(Diary.pic_draw_add object_form1)
        {
            InitializeComponent();
            pic_draw_add_object = object_form1;
            tool = LineTool;
            foreColor = Color.FromArgb(0, 0 , 0);
            eraserSize = 20;
        }

        /// <summary>
        /// 마우스가 눌리는 이벤트를 처리
        /// 처음 눌린 좌표를 start, oldMouse, mouseDownAt에 저장
        /// start는 mouseUp과 mouseMove 이벤트에서 시작 좌표로 사용
        /// oldMouse는 처음 눌린 곳의 좌표를 기억후 바로 다음의 이벤트에서 이전 좌표로 사용
        /// mouseDownAt은 mouseMove이벤트에서 최초의 좌표로 사용됨(지울수 있을것 같음)
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void draw_panel_MouseDown(object sender, System.Windows.Forms.MouseEventArgs e)
        {
            start = new Point(e.X, e.Y);
            mouseDownOrNot = MouseDownState;
            oldMouse = mouseDownAt = new Point(e.X, e.Y);
        }

        /// <summary>
        /// 마우스가 클릭된 상태를 mouseDownorNot 변수를 통해 확인
        /// 클릭된 상태라면 마우스가 이동하는 동안 최신 좌표(e.X, e.Y)와 이전 좌표(oldMouse)를 이용하여 그리기와 지우기를 반복한다.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void draw_panel_MouseMove(object sender, System.Windows.Forms.MouseEventArgs e)
        {
            drawingPen = new Pen(foreColor);
            end = new Point(e.X, e.Y);
            g = this.draw_panel_view.CreateGraphics();

            if (tool == LineTool && mouseDownOrNot == MouseDownState)
            {
                this.draw_panel_view.CreateGraphics().DrawLine(drawingPen, start, end);
                start = end;
            }
            if (tool == EraseTool && mouseDownOrNot == MouseDownState)
            {
                fillBrush = new SolidBrush(Color.White);
                g.FillEllipse(fillBrush, end.X - eraserSize / 2, end.Y - eraserSize / 2, eraserSize, eraserSize);
            }

            if (tool == RectangleTool)
            {
                if (fillOrNot == NotFill && mouseDownOrNot == MouseDownState)
                {
                    gdi.DrawRectangle(this.draw_panel_view.CreateGraphics(), mouseDownAt, new Point(e.X, e.Y), foreColor);
                    gdi.DrawRectangle(this.draw_panel_view.CreateGraphics(), mouseDownAt, oldMouse, foreColor);
                    oldMouse = new Point(e.X, e.Y);
                }
                
            }
            if (tool == ElipseTool)
            {
                if(fillOrNot == NotFill && mouseDownOrNot == MouseDownState){
                    gdi.DrawEllipse(this.draw_panel_view.CreateGraphics(), mouseDownAt, new Point(e.X, e.Y), foreColor);
                    gdi.DrawEllipse(this.draw_panel_view.CreateGraphics(), mouseDownAt, oldMouse, foreColor);
                    oldMouse = new Point(e.X, e.Y);
                }
            }

        }

        /// <summary>
        /// 눌려있던 마우스의 왼쪽 버튼이 위로 올라올때 이벤트를 처리
        /// 시작점에서 끝점까지의 이미지를 그려준다.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void draw_panel_Mouseup(object sender, System.Windows.Forms.MouseEventArgs e)
        {
            g = this.draw_panel_view.CreateGraphics();
            mouseDownOrNot = MouseUpState;
            end.X = e.X;
            end.Y = e.Y;
            width = Math.Abs(end.X - start.X);
            height = Math.Abs(end.Y - start.Y);
            start.X = Math.Min(start.X, end.X);
            start.Y = Math.Min(start.Y, end.Y);
            fillBrush = new SolidBrush(foreColor);
            drawingPen = new Pen(foreColor);

            //////////////////////////////////////////////////////
            /////tool의 값에 따라서 그리기 수행(rectangle, ellipse)
            //////////////////////////////////////////////////////
            if (tool == RectangleTool)
            {
                if (fillOrNot == Fill)
                {
                    g.FillRectangle(fillBrush, start.X, start.Y, width, height);
                }
                else if (fillOrNot == NotFill)
                {
                    gdi.DrawRectangle(this.draw_panel_view.CreateGraphics(), mouseDownAt, oldMouse, foreColor);
                    g.DrawRectangle(drawingPen, start.X, start.Y, width, height);
                }
            }
            if (tool == ElipseTool)
            {
                if (fillOrNot == Fill)
                {
                    g.FillEllipse(fillBrush, start.X, start.Y, width, height);
                }
                else if (fillOrNot == NotFill)
                {
                    gdi.DrawEllipse(this.draw_panel_view.CreateGraphics(), mouseDownAt, oldMouse, foreColor);
                    g.DrawEllipse(drawingPen, start.X, start.Y, width, height);
                }
            }
            
        }

        /// <summary>
        /// 마우스 이벤트를 통해서 그리는 기능을 입력받는다.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void erase_draw_Click(object sender, EventArgs e)
        {
            tool = EraseTool;
        }

        private void line_draw_Click(object sender, EventArgs e)
        {
            tool = LineTool;
            erase_check = 0;
        }

        private void rectangle_draw_Click(object sender, EventArgs e)
        {
            tool = RectangleTool;
            
        }

        private void Elipse_Click(object sender, EventArgs e)
        {
            tool = ElipseTool;
            
        }


        /// <summary>
        /// 도형의 fill을 처리해주는 이벤트
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void fill_draw_Click(object sender, EventArgs e)
        {
            erase_check = ~erase_check;
            if (erase_check == 0)
            {
                fillOrNot = Fill;
            }
            else
            {
                fillOrNot = NotFill;
            }
        }


        /// <summary>
        /// 마우스 이벤트를 통해서 각각의 color를 입력받고, 그리는데 사용되는 색을 설정한다.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void black_Click(object sender, EventArgs e)
        {
            foreColor = Color.Black;
        }

        private void yellow_Click(object sender, EventArgs e)
        {
            foreColor = Color.Yellow;
        }

        private void red_Click(object sender, EventArgs e)
        {
            foreColor = Color.Red;
        }

        private void green_Click(object sender, EventArgs e)
        {
            foreColor = Color.Green;
        }

        private void orange_Click(object sender, EventArgs e)
        {
            foreColor = Color.Orange;
        }

        private void blue_Click(object sender, EventArgs e)
        {
            foreColor = Color.Blue;
        }



        /// <summary>
        ///  저장 버튼의 이벤트를 통해 SaveScreenShot함수를 호출하여 draw_panel_view를 이미지로 저장한다.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void button1_Click(object sender, EventArgs e)
        {
            /*Bitmap bmp = new Bitmap(this.draw_panel_view.Width, this.draw_panel_view.Height);
            this.draw_panel_view.DrawToBitmap(bmp, new Rectangle(0, 0, this.draw_panel_view.Width, this.draw_panel_view.DisplayRectangle.Height));
            bmp.Save("panel.png", System.Drawing.Imaging.ImageFormat.Png);*/
            string filename = " ";

            //저장 경로와 file name을 설정
            
            if(pic_draw_add_object.mod_or_new == 0){
                filename = Application.StartupPath + "/UserImage/" + UserProfile.Instance().userId + "/Picture_photo/" + pic_draw_add_object.new_diary_object.all_date + ".png";
                pic_draw_add_object.new_diary_object.all_date = pic_draw_add_object.new_diary_object.all_date+ ".png";
                pic_draw_add_object.new_diary_object.check_photoOrdraw = 1;
            }
            else if(pic_draw_add_object.mod_or_new == 1){
                filename = Application.StartupPath + "/UserImage/" + UserProfile.Instance().userId + "/Picture_photo/" + pic_draw_add_object.mod_diary_object.all_date + ".png";
                pic_draw_add_object.mod_diary_object.all_date = pic_draw_add_object.mod_diary_object.all_date + ".png";
                pic_draw_add_object.mod_diary_object.check_photoOrdraw = 1;
            }

            SaveScreenShot(filename, System.Drawing.Imaging.ImageFormat.Png);
            this.Dispose();
            pic_draw_add_object.Close();            
        }

        /// <summary>
        /// CaptureScreenShot함수를 이용하여 draw_panel_view를 screenshot을 찍고, 정해진 경로에 file을 저장
        /// </summary>
        /// <param name="filename"></param>
        /// <param name="format"></param>
        /// 
        private void SaveScreenShot(string filename, System.Drawing.Imaging.ImageFormat format)
        {
            Bitmap screenShot = CaptureScreenShot();
            screenShot.Save(filename, format);
        }

        /// <summary>
        /// Saves a picture of the screen to a bitmap image.
        /// </summary>
        /// <returns>The saved bitmap.</returns>
        private Bitmap CaptureScreenShot()
        {
            // get the bounding area of the screen containing (0,0)
            // remember in a multidisplay environment you don't know which display holds this point
            Rectangle bounds = this.draw_panel_view.Bounds;

            // create the bitmap to copy the screen shot to
            Bitmap bitmap = new Bitmap(bounds.Width, bounds.Height);

            // now copy the screen image to the graphics device from the bitmap
            using (Graphics gr = Graphics.FromImage(bitmap))
            {
                Point pt = new Point();
                pt.X =  pic_draw_add_object.Location.X+ this.draw_panel_view.Location.X + 8;
                pt.Y =  pic_draw_add_object.Location.Y +  pic_draw_add_object.location_return() + this.draw_panel_view.Location.Y + 30;
                gr.CopyFromScreen(pt, Point.Empty, bounds.Size);
                //gr.CopyFromScreen(Point.Empty, Point.Empty, bounds.Size);
                
            }

            return bitmap;
        }
    }
}
